package com.lej.core.base

import android.app.Activity
import android.content.Intent
import android.os.Bundle
import androidx.activity.result.ActivityResult
import androidx.activity.result.contract.ActivityResultContracts
import androidx.fragment.app.Fragment
import androidx.fragment.app.FragmentActivity
import androidx.fragment.app.FragmentManager
import androidx.lifecycle.LifecycleOwner
import kotlin.coroutines.resume
import kotlin.coroutines.suspendCoroutine

class ReqFragment() : Fragment() {
    private var intent: Intent? = null
    private var resultCallback: (ActivityResult) -> Unit = {}

    fun setIntent(intent: Intent?): ReqFragment {
        this.intent = intent
        return this
    }

    fun setCallback(resultCallback: (ActivityResult) -> Unit): ReqFragment {
        this.resultCallback = resultCallback
        return this
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        val contract = ActivityResultContracts.StartActivityForResult()
        registerForActivityResult(contract) { resultCallback(it) }.launch(intent)
    }
}

suspend fun LifecycleOwner.startAcForResult(intent: Intent?) = when (this) {
    is FragmentActivity -> supportFragmentManager
    is Fragment -> childFragmentManager
    else -> null
}?.startAcForResult(intent)

suspend fun FragmentManager.startAcForResult(intent: Intent?) =
    suspendCoroutine<Intent?> { suspend ->
        var fragment: ReqFragment? = null
        fragment = ReqFragment()
            .setIntent(intent)
            .setCallback { result ->
                when (result.resultCode) {
                    Activity.RESULT_OK -> suspend.resume(result.data)
                    Activity.RESULT_CANCELED -> suspend.resume(null)
                    else -> suspend.resume(result.data)
                }
                fragment?.let { beginTransaction().remove(it).commit() }
            }
        beginTransaction().add(fragment, fragment.javaClass.simpleName).commitNow()
    }

fun LifecycleOwner.startAcForResult(intent: Intent?, block: (Intent?) -> Unit) {
    when (this) {
        is FragmentActivity -> supportFragmentManager
        is Fragment -> childFragmentManager
        else -> null
    }?.startAcForResult(intent, block)
}

fun FragmentManager.startAcForResult(intent: Intent?, block: (Intent?) -> Unit = {}) {
    var fragment: ReqFragment? = null
    fragment = ReqFragment()
        .setIntent(intent)
        .setCallback { result ->
            block(result.data)
            fragment?.let { beginTransaction().remove(it).commit() }
        }
    beginTransaction().add(fragment, fragment.javaClass.simpleName).commitNow()
}